from threading import Thread
import time

#-----------------------------------------------------------------------#
#------------------CLASS PROCESS----------------------------------------#
#-----------------------------------------------------------------------#

class Process(Thread):
#---------------------INSTANCIATION-------------------------------------#            
    def __init__(self,aPcb):
        self.instructions =[]
        self.pcb = aPcb
        
        
#---------------------HANDLING------------------------------------------#                    

    def addInstruction(self,anInstruction):
        if(len(self.instructions)==0):
            self.pcb.currentInstruction = anInstruction
        self.instructions.append(anInstruction)
   

    def timeOfTheFirstInstruction(self):
        return (self.intructions[0]).timeRemaining 
    
    #Pregunta si un proceso esta cargado en memoria
    def isInMemory(self,aPhysicalMemory):
        esta = False
        for i in self.instructions:
            if i in aPhysicalMemory.cells:
                esta = True
        return esta

    #Devuelve el tamanho de un proceso
    def sizeOfAProcess(self):
        return len(self.instructions)
    
    def actualPage(self,aFrameSize):
        currentInstruction = self.instructions.index((self.pcb.currentInstruction)) #Tengo la currentInstruction
        numPag = currentInstruction//aFrameSize                                 #Numero de pagina actual
        page = self.pcb.processFrames[numPag]   
        return page  
        

        
#-----------------------------------------------------------------------#
#------------------CLASS PCB--------------------------------------------#
#-----------------------------------------------------------------------#        
        
class PCB():
    
    def __init__(self,number):
        self.processID = time.time() #FIXME: Tener IDs copados proveidos por la Tabla de Procesos
        self.currentInstruction = None
        self.priority = number
        self.status = ProcessStates.READY
        # ACA TENEMOS QUE HACER REFACTOR, LAS DOS VARIABLES SIGUIENTES NO DEBERIAN IR NUNCA JUNTAS
        self.baseRegister = None
        self.processFrames = []
        
    
       
#-----------------------------------------------------------------------#
#------------------CLASS INSTRUCTION------------------------------------#
#-----------------------------------------------------------------------#        
        
class Instruction():
    
    def __init__(self,aStatus,aTime):
        self.status = aStatus
        self.timeRemaining = aTime 
    
class IOInstruction(Instruction):
    def __init__(self,aTime,aDevice):
        Instruction.__init__(self, ProcessStatus.IO, aTime)
        self.neededDevice = aDevice
    
    
class ProcessStatus():
    IO = 1
    CPU = 2
        
class ProcessStates():
    WAITING = 1
    READY = 2
    EXECUTING = 3
    FINISHED = 4

